package com.yuhuihui.common.utils;

import com.yuhuihui.common.annotation.result.ErrorInfo;
import com.yuhuihui.common.annotation.result.SuccessInfo;
import com.yuhuihui.common.enums.ResultCodeStatusEnum;

import java.lang.reflect.Method;

/**
 * controller操作ResponseBody信息替换工具类
 *
 * @author yuhh
 * @date 2023-05-25 14:40:21
 */
public final class ResponseBodyInfoUtil {

    /**
     * 线程message变量
     */
    private static final ThreadLocal<String> MESSAGE_THREAD_LOCAL = new ThreadLocal<>();

    /**
     * 线程resultCode变量
     */
    private static final ThreadLocal<ResultCodeStatusEnum> RESULT_CODE_THREAD_LOCAL = new ThreadLocal<>();

    /**
     * 线程result变量
     */
    private static final ThreadLocal<Boolean> RESULT_THREAD_LOCAL = new ThreadLocal<>();

    /**
     * 如果满足该类中有指定方法且方法上有SuccessInfo注解，则改变该线程变量的message的值
     * 因为注解是单例，所以用了迂回的方式，声明一个线程变量
     * 同一个类中无法有相同的方法名
     *
     * @param cls        指定类
     * @param methodName 指定方法名
     * @param message    需要改变的message值
     * @param resultCode 返回code
     * @author yuhh
     * @date 2023-05-25 14:40:29
     */
    public static <T> void changeMessage(Class<T> cls, String methodName, String message, ResultCodeStatusEnum resultCode) {
        changeMessage(cls, methodName, message, resultCode, true);
    }

    /**
     * 如果满足该类中有指定方法且方法上有SuccessInfo注解，则改变该线程变量的message的值
     * 因为注解是单例，所以用了迂回的方式，声明一个线程变量
     * 同一个类中无法有相同的方法名
     *
     * @param cls        指定类
     * @param methodName 指定方法名
     * @param message    需要改变的message值
     * @param resultCode 返回code
     * @param result     返回result
     * @author yuhh
     * @date 2023-05-25 14:40:41
     */
    public static <T> void changeMessage(Class<T> cls, String methodName, String message, ResultCodeStatusEnum resultCode,
                                     boolean result) {
        //如果满足该类中有指定方法且方法上有SuccessInfo或ErrorInfo注解，则改变该线程变量的message的值
        Method[] methods = cls.getDeclaredMethods();
        boolean existed;
        for (Method m : methods) {
             existed = m.getName().equals(methodName)
                    && (m.isAnnotationPresent(SuccessInfo.class) || m.isAnnotationPresent(ErrorInfo.class));
            if (existed) {
                MESSAGE_THREAD_LOCAL.set(message);
                RESULT_CODE_THREAD_LOCAL.set(resultCode);
                RESULT_THREAD_LOCAL.set(result);
                break;
            }
        }
    }

    /**
     * 获取线程变量message的值
     *
     * @return {@link String } 线程变量message的值
     * @author yuhh
     * @date 2023-05-25 14:40:48
     */
    public static String getMessage(){
        return MESSAGE_THREAD_LOCAL.get();
    }

    /**
     * 获取线程变量success的值
     *
     * @return {@link ResultCodeStatusEnum }
     * @author yuhh
     * @date 2023-05-25 14:40:53
     */
    public static ResultCodeStatusEnum getResultCode(){
        ResultCodeStatusEnum resultCode = RESULT_CODE_THREAD_LOCAL.get();
        return resultCode == null? ResultCodeStatusEnum.OK: resultCode;
    }

    /**
     * 获取线程变量result的值
     *
     * @return boolean
     * @author yuhh
     * @date 2023-05-25 14:40:58
     */

    public static boolean getResult(){
        return RESULT_THREAD_LOCAL.get() == null;
    }

    /**
     * 清除线程变量的值
     *
     * @author yuhh
     * @date 2023-05-25 14:41:07
     */
    public static void cleanThreadLocal(){
        MESSAGE_THREAD_LOCAL.remove();
        RESULT_CODE_THREAD_LOCAL.remove();
        RESULT_THREAD_LOCAL.remove();
    }

    private ResponseBodyInfoUtil(){

    }
}
